﻿using System;
using System.IO;
using System.Text;
using System.Collections.Generic;
using System.Linq;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using Blizzard.Container;
using Blizzard.Contracts;
using Blizzard.DAL;
using System.Configuration;
using Blizzard.Mapper;
using Blizzard.Scripts;
using Blizzard.Test.DataObjectsII;
//using NUnit.Framework;


namespace Blizzard.Test
{
    [TestClass]
    public class UnitTest2
    {
        //IMapper _mapper = new AttrMapper();
        AttrMapper _mapper = new AttrMapper();
        private BlizzardManager manager;
        private const string _NoProperDataFound = "NO PROPER DATA HAS BEEN FOUND IN DATABASE TO DO THIS TEST";

        [TestInitialize]
        public void initializer()
        {

            string cs = ConfigurationManager.ConnectionStrings["ForSqlClientIntegratedSecurity"].ConnectionString;

            IDAO dao = new SqlClientPlugin(cs);
            //IDAO dao = new OledbPlugin(cs);
            // IDAO dao = new ODBCPlugin(cs);

            manager = new BlizzardManager(dao, _mapper);


        }

       // [TestMethod]
        public void GenerateScripts()
        {

            DDLScript script = new DDLScript(typeof(A), typeof(B), typeof(BB), typeof(BBB), typeof(BBBB) , typeof(C));

            string createTableScript = script.GenerateScript(_mapper, new SqlServerSyntax());

            FileStream fs = new FileStream(@"D:\PROJECTS\Blizzard\trunk\Blizzard.Test\Sql\UnitTest2\SqlServerScript.txt", FileMode.Create, FileAccess.Write);
            StreamWriter sw = new StreamWriter(fs);
            sw.Write(createTableScript);
            sw.Flush();
            sw.Close();


        }

        [TestMethod]
        public void BasicInsert()
        {

            manager.ResetAllContainers();

            #region "Creating 1 A and Creating 3 Bees, 3 BBees, 3 BBBees and 3 BBBBees"

            A a = manager.CreateNewObject<A>();
            a.Name = "A_" + Guid.NewGuid();

       

            B b = manager.CreateNewObject<B>();
            b.Name = "B_" + Guid.NewGuid();
            B b2 = manager.CreateNewObject<B>();
            b2.Name = "B_" + Guid.NewGuid();
            B b3 = manager.CreateNewObject<B>();
            b3.Name = "B_" + Guid.NewGuid();



            BB bb = manager.CreateNewObject<BB>();
            bb.Name = "BB_" + Guid.NewGuid();
            BB bb2 = manager.CreateNewObject<BB>();
            bb2.Name = "BB_" + Guid.NewGuid();
            BB bb3 = manager.CreateNewObject<BB>();
            bb3.Name = "BB_" + Guid.NewGuid();


            BBB bbb = manager.CreateNewObject<BBB>();
            bbb.Name = "BBB_" + Guid.NewGuid();
            BBB bbb2 = manager.CreateNewObject<BBB>();
            bbb2.Name = "BBB_" + Guid.NewGuid();
            BBB bbb3 = manager.CreateNewObject<BBB>();
            bbb3.Name = "BBB_" + Guid.NewGuid();


            BBBB bbbb = manager.CreateNewObject<BBBB>();
            bbbb.Name = "BBBB_" + Guid.NewGuid();
            bbbb.DateCreated = DateTime.Now;  
            BBBB bbbb2 = manager.CreateNewObject<BBBB>();
            bbbb2.Name = "BBBB_" + Guid.NewGuid();
            bbbb2.DateCreated = DateTime.Now;
            BBBB bbbb3 = manager.CreateNewObject<BBBB>();
            bbbb3.Name = "BBBB_" + Guid.NewGuid();
            bbbb3.DateCreated = DateTime.Now;
#endregion

            #region "Relating the objects"

            //First relating first degree object to second degree objects

            a.bees.Add(b);
            a.bees.Add(b2);
            a.bees.Add(b3);

            a.bbees.Add(bb);
            a.bbees.Add(bb2);
            a.bbees.Add(bb3);

            a.bbbees.Add(bbb);
            a.bbbees.Add(bbb2);
            a.bbbees.Add(bbb3);


            //Now relating second degree objects to each other

            //===================<b to bb>=================

            b.BBees.Add(bb);
            b.BBees.Add(bb3);

            bb2.Bees.Add(b);
            bb2.Bees.Add(b2);
            bb2.Bees.Add(b3);

            //===================</b to bb>=================

                        
            //===================<b to bbb>=================
            bbb.Bees.Add(b);
            bbb3.Bees.Add(b);

            bbb.Bees.Add(b2);
            bbb2.Bees.Add(b2);
            bbb3.Bees.Add(b2);


            b3.BBBees.Add(bbb);
            //===================</b to bbb>=================

            #endregion

            manager.UpdateAndReset();


            //==================now testing whether the above objects and their relations are saved in database===============
            //Note that although a reset of Blizzard Object containers has been taken place, but the objects above are still
            //in scope, and we can use their values to check and compare with the values that we are going to load from database
            //(THAT MEANS THAT WE DONT NEED TO KEEP THEIR VALUE IN DIFFERENT VARIABLES).

            //naming convention: When loading (back) every objects above, we use the postfix "_loaded" for the object name


            #region "Checking existance of all objects in database one by one"

            BList<A> aas = manager.Load<A>("WHERE NAME='" + a.Name + "'");
            A a_loaded = (aas.Count > 0)? aas[0] : null;
            Assert.AreEqual(a.Name, a_loaded.Name); //looks an obvious test but you never know...
            //==========================================================================================
            BList<B> bees = manager.Load<B>("WHERE NAME='" + b.Name + "'");
            B b_loaded = (bees.Count > 0) ? bees[0] : null;
            Assert.IsNotNull(b_loaded);
            Assert.AreEqual(b.Name, b_loaded.Name); //looks an obvious test but you never know...

            BList<B> bees2 = manager.Load<B>("WHERE NAME='" + b2.Name + "'");
            B b2_loaded = (bees.Count > 0) ? bees2[0] : null;
            Assert.IsNotNull(b2_loaded);
            Assert.AreEqual(b2.Name, b2_loaded.Name); //looks an obvious test but you never know...

            BList<B> bees3 = manager.Load<B>("WHERE NAME='" + b3.Name + "'");
            B b3_loaded = (bees.Count > 0) ? bees3[0] : null;
            Assert.IsNotNull(b3_loaded);
            Assert.AreEqual(b3.Name, b3_loaded.Name); //looks an obvious test but you never know...
            //==========================================================================================
            BList<BB> bbees = manager.Load<BB>("WHERE NAME='" + bb.Name + "'");
            BB bb_loaded = (bbees.Count > 0) ? bbees[0] : null;
            Assert.IsNotNull(bb_loaded);
            Assert.AreEqual(bb.Name, bb_loaded.Name); //looks an obvious test but you never know...

            BList<BB> bbees2 = manager.Load<BB>("WHERE NAME='" + bb2.Name + "'");
            BB bb2_loaded = (bbees2.Count > 0) ? bbees2[0] : null;
            Assert.IsNotNull(bb2_loaded);
            Assert.AreEqual(bb2.Name, bb2_loaded.Name); //looks an obvious test but you never know...

            BList<BB> bbees3 = manager.Load<BB>("WHERE NAME='" + bb3.Name + "'");
            BB bb3_loaded = (bbees3.Count > 0) ? bbees3[0] : null;
            Assert.IsNotNull(bb3_loaded);
            Assert.AreEqual(bb3.Name, bb3_loaded.Name); //looks an obvious test but you never know...
            //==========================================================================================
            BList<BBB> bbbees = manager.Load<BBB>("WHERE NAME='" + bbb.Name + "'");
            BBB bbb_loaded = (bbbees.Count > 0) ? bbbees[0] : null;
            Assert.IsNotNull(bbb_loaded);
            Assert.AreEqual(bbb.Name, bbb_loaded.Name); //looks an obvious test but you never know...

            BList<BBB> bbbees2 = manager.Load<BBB>("WHERE NAME='" + bbb2.Name + "'");
            BBB bbb2_loaded = (bbbees2.Count > 0) ? bbbees2[0] : null;
            Assert.IsNotNull(bbb2_loaded);
            Assert.AreEqual(bbb2.Name, bbb2_loaded.Name); //looks an obvious test but you never know...

            BList<BBB> bbbees3 = manager.Load<BBB>("WHERE NAME='" + bbb3.Name + "'");
            BBB bbb3_loaded = (bbbees3.Count > 0) ? bbbees3[0] : null;
            Assert.IsNotNull(bbb3_loaded);
            Assert.AreEqual(bbb3.Name, bbb3_loaded.Name); //looks an obvious test but you never know...
            //==========================================================================================
            BList<BBBB> bbbbees = manager.Load<BBBB>("WHERE NAME='" + bbbb.Name + "'");
            BBBB bbbb_loaded = (bbbbees.Count > 0) ? bbbbees[0] : null;
            Assert.IsNotNull(bbbb_loaded);
            Assert.AreEqual(bbbb.Name, bbbb_loaded.Name); //looks an obvious test but you never know...

            BList<BBBB> bbbbees2 = manager.Load<BBBB>("WHERE NAME='" + bbbb2.Name + "'");
            BBBB bbbb2_loaded = (bbbbees2.Count > 0) ? bbbbees2[0] : null;
            Assert.IsNotNull(bbbb2_loaded);
            Assert.AreEqual(bbbb2.Name, bbbb2_loaded.Name); //looks an obvious test but you never know...

            BList<BBBB> bbbbees3 = manager.Load<BBBB>("WHERE NAME='" + bbbb3.Name + "'");
            BBBB bbbb3_loaded = (bbbbees3.Count > 0) ? bbbbees3[0] : null;
            Assert.IsNotNull(bbbb3_loaded);
            Assert.AreEqual(bbbb3.Name, bbbb3_loaded.Name); //looks an obvious test but you never know...


            #endregion

            #region "Checking the Relationship between First level object (Parent (A)) and Second level objects (Childeren)"

            bool hasFirstChild = false;
            bool hasSecondChild = false;
            bool hasThirdChild = false;

            foreach (B bChild in a_loaded.bees)
            {
                if (bChild == b_loaded) { hasFirstChild = true; }
                if (bChild == b2_loaded) { hasSecondChild = true; }
                if (bChild == b3_loaded) { hasThirdChild = true; }
            }

            if (!hasFirstChild || !hasSecondChild || !hasThirdChild)
            {
                Assert.Fail("Relationship between A and B is not correctly persisted.");
            }

            //================================================================

            hasFirstChild = false;
            hasSecondChild = false;
            hasThirdChild = false;

            foreach (BB bbChild in a_loaded.bbees)
            {
                if (bbChild == bb_loaded) { hasFirstChild = true; }
                if (bbChild == bb2_loaded) { hasSecondChild = true; }
                if (bbChild == bb3_loaded) { hasThirdChild = true; }
            }

            if (!hasFirstChild || !hasSecondChild || !hasThirdChild)
            {
                Assert.Fail("Relationship between A and BB is not correctly persisted.");
            }

            //================================================================

            hasFirstChild = false;
            hasSecondChild = false;
            hasThirdChild = false;

            foreach (BBB bbbChild in a_loaded.bbbees)
            {
                if (bbbChild == bbb_loaded) { hasFirstChild = true; }
                if (bbbChild == bbb2_loaded) { hasSecondChild = true; }
                if (bbbChild == bbb3_loaded) { hasThirdChild = true; }
            }

            if (!hasFirstChild || !hasSecondChild || !hasThirdChild)
            {
                Assert.Fail("Relationship between A and BBB is not correctly persisted.");
            }

     
            #endregion

            bool hasFirstAssociate = false;
            bool hasSecondAssociate = false;
            bool hasThirdAssociate = false;

            #region "Checking the Relationship between B and BB"

            foreach (BB bbAssociate in b_loaded.BBees)
            {
                if (bbAssociate == bb_loaded) { hasFirstAssociate = true; }
                if (bbAssociate == bb2_loaded) { hasSecondAssociate = true; }
                if (bbAssociate == bb3_loaded) { hasThirdAssociate = true; }
            }

            if (!hasFirstAssociate || !hasSecondAssociate || !hasThirdAssociate)
            {
                Assert.Fail("Relationship between B and BB is not correctly persisted.");
            }

            // ======================================

            hasFirstAssociate = false;

            foreach (BB bbAssociate in b2_loaded.BBees)
            {
                if (bbAssociate == bb2_loaded) { hasFirstAssociate = true; }
            }

            if (!hasFirstAssociate)
            {
                Assert.Fail("Relationship between B and BB is not correctly persisted.");
            }

            // ======================================

            hasFirstAssociate = false;

            foreach (BB bbAssociate in b3_loaded.BBees)
            {
                if (bbAssociate == bb2_loaded) { hasFirstAssociate = true; }
            }

            if (!hasFirstAssociate)
            {
                Assert.Fail("Relationship between B and BB is not correctly persisted.");
            }


            // ======================================

            hasFirstAssociate = false;
  
            foreach (B bAssociate in bb_loaded.Bees)
            {
                if (bAssociate == b_loaded) { hasFirstAssociate = true; }
            }

            if (!hasFirstAssociate)
            {
                Assert.Fail("Relationship between B and BB is not correctly persisted.");
            }


  
            // ======================================

            hasFirstAssociate = false;
            hasSecondAssociate = false;
            hasThirdAssociate = false;

            foreach (B bAssociate in bb2_loaded.Bees)
            {
                if (bAssociate == b_loaded) { hasFirstAssociate = true; }
                if (bAssociate == b2_loaded) { hasSecondAssociate = true; }
                if (bAssociate == b3_loaded) { hasThirdAssociate = true; }
            }

            if (!hasFirstAssociate || !hasSecondAssociate || !hasThirdAssociate)
            {
                Assert.Fail("Relationship between B and BB is not correctly persisted.");
            }

            // ======================================

            hasFirstAssociate = false;

            foreach (B bAssociate in bb3_loaded.Bees)
            {
                if (bAssociate == b_loaded) { hasFirstAssociate = true; }
            }

            if (!hasFirstAssociate)
            {
                Assert.Fail("Relationship between B and BB is not correctly persisted.");
            }


            #endregion

            #region "Checking the relationship between b and bbb"

            hasFirstAssociate = false;
            hasSecondAssociate = false;

            foreach (BBB bbbAssociate in b_loaded.BBBees)
            {
                if (bbbAssociate == bbb_loaded) { hasFirstAssociate = true; }
                if (bbbAssociate == bbb3_loaded) { hasSecondAssociate = true; }
            }

            if (!hasFirstAssociate || !hasSecondAssociate )
            {
                Assert.Fail("Relationship between B and BBB is not correctly persisted.");
            }

            //======================================

            hasFirstAssociate = false;
            hasSecondAssociate = false;
            hasThirdAssociate = false;

            foreach (BBB bbbAssociate in b2_loaded.BBBees)
            {
                if (bbbAssociate == bbb_loaded) { hasFirstAssociate = true; }
                if (bbbAssociate == bbb2_loaded) { hasSecondAssociate = true; }
                if (bbbAssociate == bbb3_loaded) { hasThirdAssociate = true; }
            }

            if (!hasFirstAssociate || !hasSecondAssociate || !hasThirdAssociate)
            {
                Assert.Fail("Relationship between B and BBB is not correctly persisted.");
            }
            //==========
            hasFirstAssociate = false;
     

            foreach (BBB bbbAssociate in b3_loaded.BBBees)
            {
                if (bbbAssociate == bbb_loaded) { hasFirstAssociate = true; }
            }

            if (!hasFirstAssociate)
            {
                Assert.Fail("Relationship between B and BBB is not correctly persisted.");
            }


            //======================================
            //======================================

            hasFirstAssociate = false;
            hasSecondAssociate = false;
            hasThirdAssociate = false;

            foreach (B bAssociate in bbb_loaded.Bees)
            {
                if (bAssociate == b_loaded) { hasFirstAssociate = true; }
                if (bAssociate == b2_loaded) { hasSecondAssociate = true; }
                if (bAssociate == b3_loaded) { hasThirdAssociate = true; }
            }

            if (!hasFirstAssociate || !hasSecondAssociate || !hasThirdAssociate)
            {
                Assert.Fail("Relationship between B and BBB is not correctly persisted.");
            }


            //======================================

            hasFirstAssociate = false;

            foreach (B bAssociate in bbb2_loaded.Bees)
            {
                if (bAssociate == b2_loaded) { hasFirstAssociate = true; }
            }

            if (!hasFirstAssociate )
            {
                Assert.Fail("Relationship between B and BBB is not correctly persisted.");
            }
            //======================================

            hasFirstAssociate = false;
            hasSecondAssociate = false;

            foreach (B bAssociate in bbb3_loaded.Bees)
            {
                if (bAssociate == b_loaded) { hasFirstAssociate = true; }
                if (bAssociate == b2_loaded) { hasSecondAssociate = true; }
            }

            if (!hasFirstAssociate || !hasSecondAssociate)
            {
                Assert.Fail("Relationship between B and BBB is not correctly persisted.");
            }

            #endregion
        }

        ///<General>
        ///<Created>18-MAY-2011</Created>
        ///<Modified></Modified>
        ///<NeedsRecordsInDatabase>NO</NeedsRecordsInDatabase>
        ///<InsertsItsOwnNeededData>NO</InsertsItsOwnNeededData>
        ///<UpdatesDatabase>YES</UpdatesDatabase>
        ///<Precondition></Precondition>
        ///</General>
        ///<TestCase>
        ///<step>Create one A and one B, assign A to the a property of B</step>
        ///<step>Do Update without reset</step>
        ///</TestCase>
        ///<TestResult>
        ///<Initial>A has still two bees</Initial>
        ///<Expected>A should have one B</Expected>
        ///</TestResult>
        ///<Explanation></Explanation>
        [TestMethod]
        public void UpdateWithoutReset()
        {
            manager.ResetAllContainers();

            A a = manager.CreateNewObject<A>();
            a.Name = "A_" + Guid.NewGuid();

            B b = manager.CreateNewObject<B>();
            b.Name = "B_" + Guid.NewGuid();


            b.a = a;

            manager.Update();

  
            Assert.AreEqual(1, a.bees.Count);
            Assert.AreEqual(b.Name, a.bees[0].Name);
   
        }


        ///<General>
        ///<Created>20-MAY-2011</Created>
        ///<Modified></Modified>
        ///<NeedsRecordsInDatabase>YES</NeedsRecordsInDatabase>
        ///<InsertsItsOwnNeededData>YES</InsertsItsOwnNeededData>
        ///<UpdatesDatabase>YES</UpdatesDatabase>
        ///<Precondition></Precondition>
        ///</General>
        ///<TestCase>
        ///<step>Get an A from database with two bees</step>
        ///<step>Loop through its bees and Mark the first B for deletion</step>
        ///<step>Do Update without reset</step>
        ///</TestCase>
        ///<TestResult>
        ///<Initial>A has still two bees</Initial>
        ///<Expected>A should have one B</Expected>
        ///</TestResult>
        ///<Explanation></Explanation>
        [TestMethod]
        public void UpdateWithoutReset2()
        {
            manager.ResetAllContainers();

            //================<InsertsItsOwnNeededData>=================

            A a = manager.CreateNewObject<A>();
            a.Name = "A_" + Guid.NewGuid();

            B b = manager.CreateNewObject<B>();
            b.Name = "B_" + Guid.NewGuid();

            B b2 = manager.CreateNewObject<B>();
            b2.Name = "B_" + Guid.NewGuid();
            
            b.a = a;
            b2.a = a;

            manager.UpdateAndReset();

            //================</InsertsItsOwnNeededData>=================

            A a_Loaded = manager.Load<A>("where Name='" + a.Name + "'")[0];

            foreach (B b_Inloop in a_Loaded.bees)
            {
                manager.MarkForDeletion(b_Inloop);
                break;
            }


            Assert.AreEqual(1, a_Loaded.bees.Count);//this line is not part of test, it is just for extra information

            manager.Update();
            Assert.AreEqual(1, a_Loaded.bees.Count);


        }


        ///<General>
        ///<Created>20-MAY-2011</Created>
        ///<Modified></Modified>
        ///<NeedsRecordsInDatabase>YES</NeedsRecordsInDatabase>
        ///<InsertsItsOwnNeededData>YES</InsertsItsOwnNeededData>
        ///<UpdatesDatabase>YES</UpdatesDatabase>
        ///<Precondition></Precondition>
        ///</General>
        ///<TestCase>
        ///<step>Get one A who has two bees from database</step>
        ///<step>Get also one of those bees</step>
        ///<step>Deparent the B</step>
        ///<step>Update without reset</step>
        ///</TestCase>
        ///<TestResult>
        ///<Initial>A has still two bees</Initial>
        ///<Expected>A should have only one b</Expected>
        ///</TestResult>
        ///<Explanation></Explanation>
        [TestMethod]
        public void UpdateWithoutReset3()
        {

            manager.ResetAllContainers();

            //================<InsertsItsOwnNeededData>=================

            A a = manager.CreateNewObject<A>();
            a.Name = "A_" + Guid.NewGuid();

            B b = manager.CreateNewObject<B>();
            b.Name = "B_" + Guid.NewGuid();

            B b2 = manager.CreateNewObject<B>();
            b2.Name = "B_" + Guid.NewGuid();

            b.a = a;
            b2.a = a;

            manager.UpdateAndReset();

            //================</InsertsItsOwnNeededData>=================

            A a_Loaded = manager.Load<A>("where name='" + a.Name + "'")[0];
            B b_Loaded = manager.Load<B>("where name='" + b.Name + "'")[0];


            A a_New = manager.CreateNewObject<A>();
            a_New.Name = "Some A";

            b_Loaded.a = a_New;


            Assert.AreEqual(1, a_Loaded.bees.Count); //Not part of test, just for extra information.

            manager.Update();

            Assert.AreEqual(1, a_Loaded.bees.Count);

        }


        ///<General>
        ///<Created>20-MAY-2011</Created>
        ///<Modified></Modified>
        ///<NeedsRecordsInDatabase>NO</NeedsRecordsInDatabase>
        ///<InsertsItsOwnNeededData>NO</InsertsItsOwnNeededData>
        ///<UpdatesDatabase>YES</UpdatesDatabase>
        ///<Precondition>the following fields in table: [DataObjectsII BBBB] should be Nullable, Category, Code</Precondition>
        ///</General>
        ///<TestCase>
        ///<step>Adding One BBBB object to database (letting its Category and Code field null-empty)</step>
        ///</TestCase>
        ///<TestResult>
        ///<Initial></Initial>
        ///<Expected>Despite of the fact that two properties were null. object should be persisted</Expected>
        ///</TestResult>
        ///<Explanation></Explanation>
        [TestMethod]
         public void InsertNullValues()
        {

            manager.ResetAllContainers();

            BBBB bbbb = manager.CreateNewObject<BBBB>();

            bbbb.Name = "bbbb" + Guid.NewGuid();
            bbbb.DateCreated = DateTime.Now;

            manager.UpdateAndReset();


            BBBB bbbb_Loaded = manager.Load<BBBB>("where Name = '" + bbbb.Name + "'")[0];

            Assert.AreEqual(bbbb_Loaded.Category, null);
            Assert.AreEqual(bbbb_Loaded.Code, 0);

        }


        ///<General>
        ///<Created>21 MAY 2011</Created>
        ///<Modified></Modified>
        ///<NeedsRecordsInDatabase>NO</NeedsRecordsInDatabase>
        ///<InsertsItsOwnNeededData>NO</InsertsItsOwnNeededData>
        ///<UpdatesDatabase>YES</UpdatesDatabase>
        ///<Precondition></Precondition>
        ///</General>
        ///<TestCase>
        ///<step>Create a new A object</step>
        ///<step>Mark it for deletion</step>
        ///<step>Update</step>
        ///</TestCase>
        ///<TestResult>
        ///<Initial>A is added to database</Initial>
        ///<Expected>A should not be added to database</Expected>
        ///</TestResult>
        ///<Explanation></Explanation>
        [TestMethod]
        public void NewObjectIsMarkedForDeletion()
        {

            A a = manager.CreateNewObject<A>();
            a.Name = "a_" + Guid.NewGuid();

            manager.MarkForDeletion(a);

            manager.UpdateAndReset();

            //===============================


            List<A> aees_Loaded = manager.Load<A>("where name ='" + a.Name + "'");

            Assert.AreEqual(0, aees_Loaded.Count);

        }

        ///<General>
        ///<Created>22-MAY-2011</Created>
        ///<Modified></Modified>
        ///<NeedsRecordsInDatabase>NO</NeedsRecordsInDatabase>
        ///<InsertsItsOwnNeededData>NO</InsertsItsOwnNeededData>
        ///<UpdatesDatabase>YES</UpdatesDatabase>
        ///<Precondition></Precondition>
        ///</General>
        ///<TestCase>
        ///<step>Create new A</step>
        ///<step>Update Without Reset</step>
        ///<step>Change Name property of A</step>
        ///<step>Update And Reset</step>
        ///</TestCase>
        ///<TestResult>
        ///<Initial>A change to the Name property of A object is not persisted in to database</Initial>
        ///<Expected>A change to the Name property of A object should be persisted</Expected>
        ///</TestResult>
        ///<Explanation></Explanation>
        [TestMethod]
        public void PersistingChangesToInsertedObjectAfterUpdate()
        {

            A a = manager.CreateNewObject<A>();
            a.Name = "a_" + Guid.NewGuid();

            manager.Update();

            a.Name = "Changed_" +  a.Name;

            manager.UpdateAndReset();


            A a_Loaded = manager.Load<A>(a.Id);

            Assert.AreEqual(a.Name, a_Loaded.Name);

        }

 
        
        ///<General>
        ///<Created>05-JUNE-2011</Created>
        ///<Modified>06-JUNE-2011</Modified>
        ///<NeedsDataInDatabase>YES</NeedsDataInDatabase>
        ///<PreparesItsOwnNeededData>YES</PreparesItsOwnNeededData>
        ///<UpdatesDatabase>YES</UpdatesDatabase>
        ///<Precondition></Precondition>
        ///<Note>Very important test. Strangly, before this test it was not possible to persist parent switch for composite child</Note>
        ///<ResultedChanges>
        ///<Change place="BlizzardManager.Flow_RelationPersistance">
        ///<BeforeChange>After relation persisting, the relation was getting removed from relationContainer</BeforeChange>
        ///<AfterChange>Now, After relation persisting, the relationStatus will be set to None.</AfterChange>
        ///</Change>
        ///<Change place="BlizzardManager.Flow_RelationDeletion">
        ///<BeforeChange></BeforeChange>
        ///<AfterChange>Flow L4 and L5 added</AfterChange>
        ///</Change>
        ///</ResultedChanges>
        ///</General>
        ///<TestCase>
        ///<step index="1">Create a new B and one C</step>
        ///<step index="2">Assign the B to b (parent) property of C</step>
        ///<step index="3">Load a list of A from db and assign one A from it to parent property of B</step>
        ///<step index="4">Update without reset</step>
        ///<step index="5">assign another A from the list of A to parent property of B</step>
        ///<step index="6">Update without reset</step>
        ///</TestCase>
        ///<TestResult>
        ///<InitialResult>B is deleted and its orphen C remains in database???, Aees are intact</InitialResult>
        ///<MidwayResult index="1">B is deleted and its orphen C is also deleted, Aees are intact</MidwayResult>
        ///<ExpectedResult>B should still exist in database and have new A parent and still the C child</ExpectedResult>
        ///</TestResult>
        ///<Explanation></Explanation>
        [TestMethod]
        public void UpdateParentSwitchOfaCompositeChild()
        {

            //================<PREPARATION>==================
            //MAKING SURE THAT THERE ARE AT LEAST TWO A IN DATABASE

            A a1 = manager.CreateNewObject<A>();
            A a2 = manager.CreateNewObject<A>();

            a1.Name = "A_" + Guid.NewGuid();
            a2.Name = "A_" + Guid.NewGuid();

            manager.UpdateAndReset();


            //================</PREPARATION>==================

            B b = manager.CreateNewObject<B>();
            C c = manager.CreateNewObject<C>();

            b.Name = "B_" + Guid.NewGuid();
            c.Name = "C_" + Guid.NewGuid();

            c.b = b;

            BList<A> aees = manager.Load<A>("");

            //Note: the following two loaded a are not necessarily the two Aees we inserted in the preparation
            //that was just to garantie that there are two aees in database
            A a1_Loaded = aees[0];
            A a2_Loaded = aees[1];


            b.a = a1_Loaded;
                manager.Update();
            b.a = a2_Loaded;
                manager.Update();

            BList<B> bees_loaded = manager.Load<B>("where Name = '" + b.Name + "'");
            BList<C> cees_loaded = manager.Load<C>("where Name = '" + c.Name + "'");

            if (bees_loaded.Count == 0 && cees_loaded.Count == 1)
            {
                Assert.Fail("B is deleted but C is still there (Orphan!!!)");
            }
            else if (bees_loaded.Count == 0 && cees_loaded.Count == 0)
            {
                Assert.Fail("B is deleted and C too");
            }


        }


        ///<General>
        ///<Created>06-JUNE-2011</Created>
        ///<Modified>06-JUNE-2011</Modified>
        ///<NeedsDataInDatabase>YES</NeedsDataInDatabase>
        ///<PreparesItsOwnNeededData>YES</PreparesItsOwnNeededData>
        ///<UpdatesDatabase>YES</UpdatesDatabase>
        ///<Precondition></Precondition>
        ///<Note>This test revealed an important problem, a design fault, in the system but easy solved</Note>
        ///<ResultedChanges>
        ///<Change place="BlizzardManager">
        ///<BeforeChange>Status:Broken and Status:New relations used to be handled in one loop through all relation</BeforeChange>
        ///<AfterChange>Status:Broken relations get first handled end then in a similar loop the Status:New relations get handled</AfterChange>
        ///</Change>
        ///</ResultedChanges>
        ///</General>
        ///<TestCase>
        ///<step index="1">Create a new B</step>
        ///<step index="2">Assign an existing A as its parent</step>
        ///<step index="3">Update without reset</step>
        ///<step index="4">Assign another existing A as its parent</step>
        ///<step index="5">Update without reset</step>
        ///<step index="6">Assing the A in step 2 again as its parent</step>
        ///<step index="7">Update without reset</step>
        ///</TestCase>
        ///<TestResult>
        ///<InitialResult>The third time assignement will not happen instead it leaves B as orphan in database</InitialResult>
        ///<MidwayResult index="1">Throwing exception: Another problem discovered see LoadingANoneExistingObject() test</MidwayResult>
        ///<ExpectedResult>The third time assignement should be persisted too</ExpectedResult>
        ///</TestResult>
        ///<Explanation></Explanation>
        [TestMethod]
        public void UpdateParentSwitchOfaCompositeChild2()
        {

            //================<PREPARATION>==================
            //MAKING SURE THAT THERE ARE AT LEAST TWO A IN DATABASE

            A a1 = manager.CreateNewObject<A>();
            A a2 = manager.CreateNewObject<A>();

            a1.Name = "A_" +Guid.NewGuid();
            a2.Name = "A_" +Guid.NewGuid();

            manager.UpdateAndReset();


            //================</PREPARATION>==================

            B b = manager.CreateNewObject<B>();
            b.Name = "B_" + Guid.NewGuid();
 
            BList<A> aees = manager.Load<A>("");

            //Note: the following two loaded a are not necessarily the two Aees we inserted in the preparation
            //that was just to garantie that there are two aees in database
            A a1_Loaded = aees[0];
            A a2_Loaded = aees[1];


            b.a = a1_Loaded;
            manager.Update();
            b.a = a2_Loaded;
            manager.Update();
            //===============
            b.a = a1_Loaded;
            manager.Update();
   

            manager.ResetAllContainers();

            B b_loaded = manager.Load<B>("where Name = '" + b.Name + "'")[0];

            Assert.IsNotNull(b_loaded.a);


        }

        ///<General>
        ///<Created>11 JUNE 2011</Created>
        ///<Modified>11 JUNE 2011</Modified>
        ///<NeedsDataInDatabase>No</NeedsDataInDatabase>
        ///<PreparesItsOwnNeededData></PreparesItsOwnNeededData>
        ///<UpdatesDatabase>Yes</UpdatesDatabase>
        ///<Precondition></Precondition>
        ///<Note>Solving this problem also lead to a drastic change in Blizzard, the concept of default relation is completely removed, Instead, now in update method a loop in NewObjectContainer will happen </Note>
        ///<ResultedChanges>
        ///<Change place="Instantiate(), update() and many other places">
        ///<BeforeChange>In instantiate method before knowing whether an object exist or not it would make a default relation for object</BeforeChange>
        ///<AfterChange>all default relations are removed from Blizzard, instead in update method a loop in NewObjectContainer will happen</AfterChange>
        ///</Change>
        ///</ResultedChanges>
        ///</General>
        ///<TestCase>
        ///<step index="1">Load an object that you know it does not exist in database</step>
        ///<step index="2">Update database</step>
        ///</TestCase>
        ///<TestResult>
        ///<InitialResult>throws an database exception, mostly an out of range date or sometimes null Name</InitialResult>
        ///<MidwayResult index="1"></MidwayResult>
        ///<ExpectedResult>Should not throw any exception</ExpectedResult>
        ///</TestResult>
        ///<Explanation>Source of problem: a default relation was created even for a non existing object, in update time, blizzard loops through all relations regardless of whether it exists in DBObjectContainer or NewObjectContainer it will try to persist it. which ofcourse comes to problem with a null object</Explanation>
        [TestMethod]
        public void LoadingANoneExistingObject()
        {

            BBBB bbbb = manager.Load<BBBB>(2);

            manager.Update();

        }

         

    }

}



#region "XML DOCUMENTATION TEMPLATE"

///<General>
///<Created></Created>
///<Modified></Modified>
///<NeedsDataInDatabase></NeedsDataInDatabase>
///<PreparesItsOwnNeededData></PreparesItsOwnNeededData>
///<UpdatesDatabase></UpdatesDatabase>
///<Precondition></Precondition>
///<Note></Note>
///<ResultedChanges>
///<Change place="">
///<BeforeChange></BeforeChange>
///<AfterChange></AfterChange>
///</Change>
///</ResultedChanges>
///</General>
///<TestCase>
///<step index="1"></step>
///</TestCase>
///<TestResult>
///<InitialResult></InitialResult>
///<MidwayResult index="1"></MidwayResult>
///<ExpectedResult></ExpectedResult>
///</TestResult>
///<Explanation></Explanation>

#endregion 
